﻿using System;
using GodProject.peoples;

namespace WebGodServer.Database
{
  internal class ResultQueryMatcher
  {
    internal static bool IsMatch(SearchResult result, SearchQuery query)
    {
      return IsChildMatch(result, query)
             && IsParentMatch(result, query);
    }


    private static bool IsParentMatch(SearchResult result, SearchQuery query)
    {
      Parent parent = result.Parent;
      if (!IsStringContains(parent.Name, query.ParentName))
      {
        return false;
      }

      if (!IsIntervalContains(parent.Age, query.ParentAge))
      {
        return false;
      }

      return true;
    }

    private static bool IsChildMatch(SearchResult result, SearchQuery query)
    {
      Student student = result.Child;
      if (!IsStringContains(student.Name, query.ChildName))
      {
        return false;
      }

      if (!IsIntervalContains(student.Age, query.ChildAge))
      {
        return false;
      }

      if (!IsMatchSex(student.Sex, query.ChildSex))
      {
        return false;
      }

      Botan botan = student as Botan;
      if (botan != null && !IsIntervalContains(botan.AverageMark, query.AverageMark))
      {
        return false;
      }

      return true;
    }

    private static bool IsStringContains(string input, string part)
    {
      return input.ToLower().Contains(part.ToLower());
    }

    private static bool IsIntervalContains<T>(T value, SearchQuery.Interval<T> interval)
      where T : IComparable<T>
    {
      return interval == null ||
             (value.CompareTo(interval.To) <= 0
              && value.CompareTo(interval.From) >= 0);
    }

    private static bool IsMatchSex(Sex childSex, SearchQuery.QuerySex sex)
    {
      return sex == SearchQuery.QuerySex.All
             || (childSex == Sex.Male
                 && sex == SearchQuery.QuerySex.Male)
             || (childSex == Sex.Female
                 && sex == SearchQuery.QuerySex.Female);
    }
  }
}
